#ifndef __PLATFORM_OAI_NODE_H__
#define __PLATFORM_OAI_NODE_H__

#include "platform/oTypes.h"
#include "platform/oProperty.h"

namespace platform
{
	class oUnit;
	class oAILeaf;

	class oDLL oInstinct: public CCObject
	{
	public:
		void install(oUnit* unit);
		void uninstall(oUnit* unit);
		~oInstinct();
		void onInstinctPropertyChanged(oUnit* unit, float oldValue, float newValue);
		static oInstinct* create(const string& propName, oAILeaf* node);
	protected:
		oInstinct(const string& propName, oAILeaf* node);
	private:
		string _propName;
		oAILeaf* _actionNode;
		oPropertyHandler _handler;
	};

	/** @brief Behavior Tree base node */

	class oDLL oAILeaf: public CCObject
	{
	public:
		virtual bool doAction() = 0;
	};

	class oAINode: public oAILeaf
	{
	public:
		virtual ~oAINode();
		virtual void addChild(oAILeaf* node);
		virtual void removeChild(oAILeaf* node);
		virtual void clear();
		const vector<oAILeaf*>& getChildren() const;
	protected:
		vector<oAILeaf*> _children;
	};

	/** @brief Selector Node */
	class oSelNode: public oAINode
	{
	public:
		virtual bool doAction();
		static oSelNode* create();
	protected:
		oSelNode();
	};

	/** @brief Sequence Node */
	class oSeqNode: public oAINode
	{
	public:
		virtual bool doAction();
		static oSeqNode* create();
	protected:
		oSeqNode();
	};

	/** @brief Parallel Selector Node */
	class oParSelNode: public oAINode
	{
	public:
		virtual bool doAction();
		static oParSelNode* create();
	protected:
		oParSelNode();
	};

	/** @brief Parallel Sequence Node */
	class oParSeqNode: public oAINode
	{
	public:
		virtual bool doAction();
		static oParSeqNode* create();
	protected:
		oParSeqNode();
	};

	class oActNode: public oAILeaf
	{
	public:
		virtual bool doAction();
		static oAILeaf* create();
	private:
		int _actionId;
	};

	class oCompare;

	class oConNode0: public oAILeaf
	{
	public:
		virtual ~oConNode0();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oRelation _relation;
		oCompare* _compare;
	};

	class oConNode1: public oAILeaf
	{
	public:
		virtual ~oConNode1();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oRelation _relation;
		uint32 _type;
		oCompare* _compare;
	};

	class oConNode2: public oAILeaf
	{
	public:
		virtual ~oConNode2();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oRelation _relation;
		oCompare* _compareDistance;
		oCompare* _compareCount;
	};

	class oConNode3: public oAILeaf
	{
	public:
		virtual ~oConNode3();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oRelation _relation;
		oCompare* _compareHp;
		oCompare* _compareCount;
	};

	class oConNode4: public oAILeaf
	{
	public:
		virtual ~oConNode4();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oRelation _relation;
		oCompare* _comparePercent;
		oCompare* _compareCount;
	};

	class oConNode5: public oAILeaf
	{
	public:
		virtual ~oConNode5();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oRelation _relation;
		string _name;
		oCompare* _compareProperty;
		oCompare* _compareCount;
	};

	class oConNode6: public oAILeaf
	{
	public:
		virtual ~oConNode6();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oCompare* _compare;
	};

	class oConNode7: public oAILeaf
	{
	public:
		virtual ~oConNode7();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oCompare* _compare;
	};

	class oConNode8: public oAILeaf
	{
	public:
		virtual ~oConNode8();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		string _name;
		oCompare* _compare;
	};

	class oConNode9: public oAILeaf
	{
	public:
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oRelation _relation;
		uint32 _action;
	};

	class oConNode10: public oAILeaf
	{
	public:
		virtual ~oConNode10();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oRelation _relation;
		oCompare* _compare;
	};

	class oConNode11: public oAILeaf
	{
	public:
		virtual ~oConNode11();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oRelation _relation;
		oCompare* _compare;
	};

	class oConNode12: public oAILeaf
	{
	public:
		virtual ~oConNode12();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oRelation _relation;
		oCompare* _compare;
	};

	class oConNode13: public oAILeaf
	{
	public:
		virtual ~oConNode13();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oRelation _relation;
		string _name;
		oCompare* _compare;
	};

	class oConNode14: public oAILeaf
	{
	public:
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oRelation _relation;
		uint32 _action;
	};

	class oConNode15: public oAILeaf
	{
	public:
		virtual ~oConNode15();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oRelation _relation;
		oCompare* _compare;
	};

	class oConNode16: public oAILeaf
	{
	public:
		virtual ~oConNode16();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oRelation _relation;
		oCompare* _compare;
	};

	class oConNode17: public oAILeaf
	{
	public:
		virtual ~oConNode17();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oRelation _relation;
		string _name;
		oCompare* _compare;
	};

	class oConNode18: public oAILeaf
	{
	public:
		virtual bool doAction();
		static oAILeaf* create();
	private:
		int _tag;
		uint32 _action;
	};

	class oConNode19: public oAILeaf
	{
	public:
		virtual ~oConNode19();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		int _tag;
		oCompare* _compare;
	};

	class oConNode20: public oAILeaf
	{
	public:
		virtual ~oConNode20();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		int _tag;
		oCompare* _compare;
	};

	class oConNode21: public oAILeaf
	{
	public:
		virtual ~oConNode21();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		int _tag;
		oCompare* _compare;
	};

	class oConNode22: public oAILeaf
	{
	public:
		virtual ~oConNode22();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		int _tag;
		string _name;
		oCompare* _compare;
	};

	class oConNode23: public oAILeaf
	{
	public:
		virtual bool doAction();
		static oAILeaf* create();
	};

	class oConNode24: public oAILeaf
	{
	public:
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oRelation _relation;
	};

	class oConNode25: public oAILeaf
	{
	public:
		virtual bool doAction();
		static oAILeaf* create();
	private:
		int _tag;
	};

	class oConNode26: public oAILeaf
	{
	public:
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oRelation _relation;
	};

	class oConNode27: public oAILeaf
	{
	public:
		virtual bool doAction();
		static oAILeaf* create();
	private:
		int _tag;
	};

	class oConNode28: public oAILeaf
	{
	public:
		virtual ~oConNode28();
		virtual bool doAction();
		static oAILeaf* create();
	private:
		oCompare* _compare;
	};

	typedef oAILeaf* (*oConNodeFunc)();

	class oConNode
	{
	public:
		static oAILeaf* create(uint32 index);
	private:
		static const oConNodeFunc creates[];
		static const uint32 MAX_CONNODE;
	};
}

#endif
